/* Copyright (c) 2007 Scott Lembcke
 * 
 * Permission is hereby granted, free of charge, to any person obtaining a copy
 * of this software and associated documentation files (the "Software"), to deal
 * in the Software without restriction, including without limitation the rights
 * to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
 * copies of the Software, and to permit persons to whom the Software is
 * furnished to do so, subject to the following conditions:
 * 
 * The above copyright notice and this permission notice shall be included in
 * all copies or substantial portions of the Software.
 * 
 * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
 * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
 * FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
 * AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
 * LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
 * OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE
 * SOFTWARE.
 */
 
#include <stdlib.h>
#include <stdio.h>
#include <math.h>

#include "chipmunk.h"

extern cpSpace *space;
extern cpBody *staticBody;

void demo6_update(int ticks)
{
	int steps = 2;
	cpFloat dt = 1.0/60.0/(cpFloat)steps;
	
	for(int i=0; i<steps; i++){
		cpSpaceStep(space, dt);
	}
}

static void
add_tilty_thing(cpVect p){
	cpBody *body = cpBodyNew(1.0, 785.7);
	cpSpaceAddBody(space, body);
	body->p = p;
	body->w = 1.0;
//	cpBodySetAngle(body, 0.1);
	
	// add segments
	cpShape *shape;
	shape = cpSegmentShapeNew(body, cpv(-25, -8.9), cpv(25, -8.9), 0.0);
	cpSpaceAddShape(space, shape);
	shape = cpSegmentShapeNew(body, cpv(0, -8.9), cpv(0, 31.1), 0.0);
	cpSpaceAddShape(space, shape);
	
	// add joints
	cpSpaceAddJoint(space, cpPivotJointNew(staticBody, body, cpv(p.x, p.y - 8.9)));
	cpSpaceAddJoint(space, cpSlideJointNew(staticBody, body, cpv(p.x, p.y + 30), cpv(0, 30), 0.0, 20.0));
}

static void
add_ball(cpVect p){
	cpFloat radius = 15.0f;
	cpFloat mass = 3.0;
	
	cpBody *body = cpBodyNew(mass, cpMomentForCircle(mass, 0.0, radius, cpvzero));
	body->p = p;
	cpSpaceAddBody(space, body);
	
	cpShape *shape = cpCircleShapeNew(body, radius, cpvzero);
	shape->e = 0.0; shape->u = 1.5;
	cpSpaceAddShape(space, shape);
}

void demo6_init(void)
{
	staticBody = cpBodyNew(INFINITY, INFINITY);
	
	cpResetShapeIdCounter();
	space = cpSpaceNew();
	cpSpaceResizeStaticHash(space, 20.0, 999);
	space->gravity = cpv(0, -300);
	
	cpShape *shape;
	
	// Screen border
	shape = cpSegmentShapeNew(staticBody, cpv(-320,-240), cpv(-320,240), 0.0f);
	shape->e = 1.0; shape->u = 1.0;
	cpSpaceAddStaticShape(space, shape);

	shape = cpSegmentShapeNew(staticBody, cpv(320,-240), cpv(320,240), 0.0f);
	shape->e = 1.0; shape->u = 1.0;
	cpSpaceAddStaticShape(space, shape);

	shape = cpSegmentShapeNew(staticBody, cpv(-320,-240), cpv(320,-240), 0.0f);
	shape->e = 1.0; shape->u = 1.0;
	cpSpaceAddStaticShape(space, shape);
	
	// Feeder
	shape = cpSegmentShapeNew(staticBody, cpv(-320, 200), cpv(-20, 150), 0.0f);
	shape->e = 1.0; shape->u = 0.1;
	cpSpaceAddStaticShape(space, shape);
	
	shape = cpSegmentShapeNew(staticBody, cpv(15, 150), cpv(20, 240), 0.0f);
	shape->e = 1.0; shape->u = 0.1;
	cpSpaceAddStaticShape(space, shape);
	
	// Balls
	for(int i=0; i<8; i++)
		for(int j=0; j<1; j++)
			add_ball(cpv(-300 + 30*i, 215 + 40*j));
	
	// Tilty Thingys
	add_tilty_thing(cpv(0, 90));
	
	add_tilty_thing(cpv(60, 30));
	add_tilty_thing(cpv(-60, 30));
	
	// Slots
	shape = cpSegmentShapeNew(staticBody, cpv(0, -240), cpv(0, 0), 0.0f);
	shape->e = 1.0; shape->u = 0.1;
	cpSpaceAddStaticShape(space, shape);

	shape = cpSegmentShapeNew(staticBody, cpv(60, -240), cpv(60, 0), 0.0f);
	shape->e = 1.0; shape->u = 0.1;
	cpSpaceAddStaticShape(space, shape);

	shape = cpSegmentShapeNew(staticBody, cpv(-60, -240), cpv(-60, 0), 0.0f);
	shape->e = 1.0; shape->u = 0.1;
	cpSpaceAddStaticShape(space, shape);
}
